﻿using System;
using System.Collections.Generic;
#if DEBUG
using System.Diagnostics;
#endif // #if DEBUG
using System.Linq;
using System.Text;
using FRL.DebtChased.WebServices;

namespace FRL.DebtChased.Repository
{

	/// <summary>
	/// Extensions to the Agent model
	/// </summary>
	public partial class Agent
	{

		/////////////////////////////////////////////////////////////
		// Attributes

		public Definitions.eAgentType AgentType
		{
			get { return (Definitions.eAgentType)this.fdAgentType; }
			set { this.fdAgentType = (int)value; }
		}

		/////////////////////////////////////////////////////////////
		// Operations

		public bool CanDelete()
		{

			// Can this agent be deleted
			return true;

		}

#if DEBUG
		public void Dump()
		{

			// Dump agent members
			Console.WriteLine("Agent[{0}] Type={1} Name={2} Website={3}", this._AgentId, this.AgentType, this._Name, this._Website);
			Console.WriteLine("   Notes={0}", this._Notes);

		}
#endif // #if DEBUG

		/////////////////////////////////////////////////////////////
		// Static Operations

		public static AgentTransport GetAgentTransport(DebtChasedEntities ent, int iAgentId)
		{

			// Declare return variable
			AgentTransport Ftmp = null;

			// Load the agent details
			Agent agent = (from a in ent.Agents.Include("AgentBankAccounts")
						  where (a.AgentId == iAgentId)
						  select a).FirstOrDefault();

			// If record found...
			if (agent != null)
			{

				// Set object members
				Ftmp = new AgentTransport();
				Ftmp.AgentId = iAgentId;
				Ftmp.AgentType = agent._fdAgentType;
				Ftmp.CoverageCountryCodes = agent.CountryCodes.Split(',').ToList();
				Ftmp.Name = agent.Name;
				Ftmp.Notes = agent.Notes;
				Ftmp.Website = agent.Website;
				Ftmp.UseAccountCommissionRate = agent.UseAccountCommissionRate;
				Ftmp.SpecificCommissionRatePerc = agent.SpecificCommissionRatePerc;

				// Get the bank accounts
				Ftmp.BankAccounts = AgentBankAccount.GetTransportList(agent);

				// Get the contacts
				Ftmp.Contacts = AgentContact.GetTransportList(agent);

			}

			// Return variable
			return Ftmp;

		}

		public static string SetAgentTransport( DebtChasedEntities ent, AgentTransport agentTransport, int iUserId )
		{
#if DEBUG
			Debug.Assert(agentTransport.Contacts != null);
			Debug.Assert(agentTransport.BankAccounts != null);
#endif // #if DEBUG

			// Declare return variable
			string strError = null;

			// Compose coverage string
			StringBuilder sbCoverage = new StringBuilder();
			foreach (string strCode in agentTransport.CoverageCountryCodes)
			{
				if (sbCoverage.Length > 0)
					sbCoverage.Append(",");
				sbCoverage.Append(strCode);
			}

			try
			{

				// Get all agent objects
				Agent currentAgent = null;
				if (agentTransport.AgentId == 0)
				{

					// Create a new agent
					currentAgent = new Agent();
					ent.Agents.AddObject(currentAgent);

				}
				else
				{

					// Load the agent details including bank acccounts
					currentAgent = (from a in ent.Agents.Include("AgentBankAccounts").Include("AgentContacts")
									where (a.AgentId == agentTransport.AgentId)
									select a).First();
#if DEBUG
					Debug.Assert(currentAgent != null);
#endif // #if DEBUG

				}

				// Track user activity
				UserAction.Session session = new UserAction.Session(iUserId, currentAgent, agentTransport.Name);

				// Process bank accounts
				AgentBankAccount.InterCursorSetFromTransport(ent, session, currentAgent, agentTransport, iUserId);

				// Process contacts
				Dictionary<int, AgentContact> contactMap = new Dictionary<int, AgentContact>();
				AgentContact.InterCursorSetFromTransport(ent, session, currentAgent, agentTransport, contactMap, iUserId);

				// Update the agent
				if (currentAgent.fdAgentType != agentTransport.AgentType)
					currentAgent.fdAgentType = agentTransport.AgentType;

				if(currentAgent.CountryCodes != sbCoverage.ToString())
					currentAgent.CountryCodes = sbCoverage.ToString();

				if(currentAgent.Name != agentTransport.Name)
					currentAgent.Name = agentTransport.Name;

				if(currentAgent.Notes != agentTransport.Notes)
					currentAgent.Notes = agentTransport.Notes;

				if(currentAgent.Website != agentTransport.Website)
					currentAgent.Website = agentTransport.Website;

				if(currentAgent.UseAccountCommissionRate != agentTransport.UseAccountCommissionRate)
					currentAgent.UseAccountCommissionRate = agentTransport.UseAccountCommissionRate;

				if (currentAgent.SpecificCommissionRatePerc != agentTransport.SpecificCommissionRatePerc)
					currentAgent.SpecificCommissionRatePerc = agentTransport.SpecificCommissionRatePerc;

				// If session has changes...
				if (session.HasChanges())
				{

					// Save changes
					ent.SaveChanges();

					// Update agent
					if (agentTransport.AgentId == 0)
						agentTransport.AgentId = currentAgent.AgentId;
#if DEBUG
					else
						Debug.Assert(agentTransport.AgentId == currentAgent.AgentId);
#endif // #if DEBUG

					// Add the session objects
					session.SaveChanges(ent);

				}

			}
			catch (Exception x)
			{

				// Handle exception
				strError = ErrorProcessing.HandleException(x, "save agent", iUserId);

			}

			// Return variable
			return strError;

		}

		public static List<AgentSummaryTransport> TransportSearch(DebtChasedEntities ent, string strCountryCode, int iUserId)
		{

			// Declare return variable
			List<AgentSummaryTransport> Ftmp = new List<AgentSummaryTransport>();

			try
			{

				// Format search string
				string strSearch;
				if (strCountryCode.Contains("%"))
					strSearch = strCountryCode;
				else
					strSearch = string.Format("%{0}%", strCountryCode);

				// Load from SP function
				var results = ent.SearchAgentsProc(strSearch);
				foreach (var result in results)
				{

					// Load the return variable
					AgentSummaryTransport ast = new AgentSummaryTransport();
					Ftmp.Add(ast);
					ast.AgentId = result.fdAgentId;
					ast.AgentType = (result.fdAgentType == (int)Definitions.eAgentType.Agent) ? "Agent" : "Solicitor";
					ast.CoverageCountryCodes = result.fdCountryCodes;
					ast.Contacts = result.fdContacts;
					ast.Name = result.fdName;

				}

			}
			catch (Exception x)
			{

				// Process exception
				ErrorProcessing.HandleException(x, "search agents", iUserId);

				// Nullify list
				Ftmp = null;

			}

			// Return variable
			return Ftmp;

		}

	}

}
